#include "RenderManager.h"
#include "Define.h"
#include "DebugLog.h"
#ifdef _WINDOWS
	#include <Windows.h>
#endif

RenderManager::RenderManager(std::shared_ptr<sf::RenderWindow> window, std::shared_ptr<sf::View> view)
{
	_window = window;
	_view = view;
	_frontView = std::shared_ptr<sf::View>(new sf::View(sf::FloatRect(0, 0, VIRTUAL_SCREEN_WIDTH, VIRTUAL_SCREEN_HEIGHT)));
	_frontView->setCenter(VSW_05, VSH_05);
	_renderState = RS_NONE;
}

RenderManager::~RenderManager(void){}

void RenderManager::beginRender()
{
	_window->setView(*_view);
	_window->clear(sf::Color::Black);
}

void RenderManager::draw(sf::Drawable& sprite)
{
	switch (_renderState)
	{
	case RS_WINDOW:
		_window->draw(sprite);
		break;
	case RS_BACKBUFFER:
		_renderTexture.draw(sprite);
		break;
	}
}

void RenderManager::draw(sf::Drawable& sprite, sf::Shader& shader)
{
	sf::RenderStates states;
	states.shader = &shader;
	switch (_renderState)
	{
	case RS_WINDOW:
		_window->draw(sprite, states);
		break;
	case RS_BACKBUFFER:
		_renderTexture.draw(sprite, states);
		break;
	}
}

void RenderManager::endRender()
{
	switch (_renderState)
	{
	case RS_NONE:
			Debug::log("ERROR: System is trying to render without setting render state");
			#ifdef _WINDOWS
				MessageBox(NULL, "System is trying to render without setting render state.", "ERROR", MB_ICONSTOP);
			#endif
		break;
	case RS_WINDOW:
		_window->display();
		break;
	case RS_BACKBUFFER:
		_renderTexture.display();
		_window->clear();
		sf::Sprite sprite(_renderTexture.getTexture());
		_window->draw(sprite);
		_window->display();
		break;
	}
}

void RenderManager::setView(unsigned int view)
{
	switch (view)
	{
	case VIEW_STANDARD:
		_window->setView(*_view);
		break;
	case VIEW_FRONT:
		_window->setView(*_frontView);
		break;
	}
}

void RenderManager::setRenderState(unsigned int renderState)
{
	//if (renderState != RS_WINDOW || renderState != RS_BACKBUFFER)
	//TODO: fix

	_renderState = static_cast<RenderState>(renderState);
	
	if (_renderState == RS_BACKBUFFER)
	{
		if (!_renderTexture.create(static_cast<unsigned int>(VIRTUAL_SCREEN_WIDTH), static_cast<unsigned int>(VIRTUAL_SCREEN_HEIGHT)))
		{
			Debug::log("ERROR: Cannot create backbuffer render target");
			#ifdef _WINDOWS
				MessageBox(NULL, "Cannot create backbuffer render target. Switching to direct rendering", "ERROR", MB_ICONSTOP);
			#endif
			_renderState = RS_WINDOW;
		}
	}
}
